home *** CD-ROM | disk | FTP | other *** search
/ Sky at Night 2006 September / SAN CD 9-2006 CD-ROM 16.iso / pc / Software / Network Telescope Control / NTC-Setup.Exe / Source / ntc_ciel_client_control.pas < prev    next >
Encoding:
Pascal/Delphi Source File  |  2006-03-24  |  33.5 KB  |  1,545 lines

  1. unit ntc_ciel_client_control;
  2. {
  3.     Copyright (C) 2004 - 2006 Andrew Sprott
  4.  
  5.     http://astronomy.crysania.co.uk
  6.     astro@trefach.co.uk
  7.  
  8.     This program is free software; you can redistribute it and/or
  9.     modify it under the terms of the GNU General Public License
  10.     as published by the Free Software Foundation; either version 2
  11.     of the License, or (at your option) any later version.
  12.  
  13.     This program is distributed in the hope that it will be useful,
  14.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  15.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16.     GNU General Public License for more details.
  17.  
  18.     You should have received a copy of the GNU General Public License
  19.     along with this program; if not, write to the Free Software
  20.     Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  21. }
  22.  
  23. interface
  24.  
  25. uses
  26.     Windows,
  27.     Messages,
  28.     SysUtils,
  29.     Variants,
  30.     Classes,
  31.     Graphics,
  32.     Controls,
  33.     Forms,
  34.     Dialogs,
  35.     StdCtrls,
  36.     ExtCtrls,
  37.     Buttons,
  38.     inifiles,
  39.     ComCtrls,
  40.  
  41.     ntc_ciel_client_form;
  42.  
  43. const
  44.     { scope types }
  45.     max_speeds=25;
  46.     window_track_max=50;
  47.     window_track_step=2;
  48.     window_method=0;
  49.     degree_method=1;
  50.     window_percent_default=80;
  51.     move_degrees_default=0;
  52.     move_minutes_default=0;
  53.     move_seconds_default=1;
  54.     { basics }
  55.     minutes_in_degree=60;
  56.     seconds_in_minute=60;
  57.     max_degrees=360;
  58.     max_degrees_dec=90;
  59.     max_hours=24;
  60.     cr=#13;
  61.  
  62. type
  63.     buttons_type_set=(
  64.         button_north,
  65.         button_south,
  66.         button_east,
  67.         button_west);
  68.     buttons_type=set of buttons_type_set;
  69.  
  70. const
  71.     buttons_all:buttons_type=[
  72.         button_north,
  73.         button_south,
  74.         button_east,
  75.         button_west];
  76.  
  77. type
  78.     Tscope_control = class(tform)
  79.         control_panel: TPanel;
  80.         slew_group: TGroupBox;
  81.         north_button: TSpeedButton;
  82.         east_button: TSpeedButton;
  83.         west_button: TSpeedButton;
  84.         south_button: TSpeedButton;
  85.     stop_button: TSpeedButton;
  86.         north_label: TLabel;
  87.         west_label: TLabel;
  88.         south_label: TLabel;
  89.         east_label: TLabel;
  90.         connect_group: TGroupBox;
  91.         connect_button: TSpeedButton;
  92.         disconnect_button: TSpeedButton;
  93.         led_display: TEdit;
  94.         goto_group: TGroupBox;
  95.         ra_hours_edit: TEdit;
  96.         ra_minutes_edit: TEdit;
  97.         ra_seconds_edit: TEdit;
  98.         dec_degrees_edit: TEdit;
  99.         dec_minutes_edit: TEdit;
  100.         dec_seconds_edit: TEdit;
  101.         ra_label: TLabel;
  102.         dec_label: TLabel;
  103.         hours_label: TLabel;
  104.         ra_minutes_label: TLabel;
  105.         ra_seconds_label: TLabel;
  106.         dec_minutes_label: TLabel;
  107.         dec_seconds_label: TLabel;
  108.         degrees_label: TLabel;
  109.         goto_button: TBitBtn;
  110.         locked_check: TCheckBox;
  111.         ra_hours_up_down: TUpDown;
  112.     dec_degrees_up_down: TUpDown;
  113.         ra_minutes_up_down: TUpDown;
  114.         dec_minutes_up_down: TUpDown;
  115.         ra_seconds_up_down: TUpDown;
  116.         dec_seconds_up_down: TUpDown;
  117.         refresh_button: TBitBtn;
  118.         move_units_group: TGroupBox;
  119.         move_degrees_up_down: TUpDown;
  120.         move_minutes_up_down: TUpDown;
  121.         move_degrees_edit: TEdit;
  122.         move_minutes_edit: TEdit;
  123.         move_seconds_edit: TEdit;
  124.         move_seconds_up_down: TUpDown;
  125.         move_seconds_label: TLabel;
  126.         move_minutes_label: TLabel;
  127.         move_degrees_label: TLabel;
  128.         window_move_button: TSpeedButton;
  129.         degree_move_button: TSpeedButton;
  130.         move_window_group: TGroupBox;
  131.         degrees_edit: TEdit;
  132.         window_track: TTrackBar;
  133.         window_label: TLabel;
  134.  
  135.         { form functions }
  136.         procedure formcreate(
  137.             Sender:TObject);
  138.  
  139.         procedure form_close_query(
  140.                     Sender: TObject;
  141.             var CanClose: Boolean);
  142.  
  143.         { scope linkage }
  144.         procedure flip_buttons(
  145.             toggle:boolean);
  146.  
  147.         procedure change_panel(
  148.             toggle:boolean);
  149.  
  150.         function connect_to_scope
  151.             :boolean;
  152.  
  153.         function disconnect_from_scope
  154.             :boolean;
  155.  
  156.         { directional controls }
  157.         procedure stop_failed;
  158.  
  159.         procedure move_down;
  160.         procedure move_up;
  161.         procedure move_left;
  162.         procedure move_right;
  163.  
  164.         procedure move_distance(
  165.             d:string);
  166.  
  167.         procedure north_button_down(
  168.             Sender:TObject);
  169.  
  170.         procedure south_button_down(
  171.             Sender:TObject);
  172.  
  173.         procedure east_button_down(
  174.             Sender:TObject);
  175.  
  176.         procedure west_button_down(
  177.             Sender:TObject);
  178.  
  179.         procedure stop_button_down(
  180.             Sender:TObject);
  181.  
  182.         procedure stop_scope;
  183.  
  184.         { goto }
  185.         procedure go_to;
  186.  
  187.         { speed controls }
  188.         procedure update_speed_group(
  189.             speed_box:tpanel;
  190.             first_speed_button:tspeedbutton;
  191.             start_speed,
  192.             speed_count:integer;
  193.             event:TNotifyEvent;
  194.             can_do:boolean);
  195.  
  196.         function set_slew_speed(
  197.             speed_box:tpanel)
  198.             :integer;
  199.  
  200.         { logging }
  201.         procedure write_status_log(
  202.             e:string);
  203.  
  204.         { configuration }
  205.         procedure load_settings;
  206.  
  207.         procedure save_settings;
  208.  
  209.         { utilites }
  210.         procedure change_window_method;
  211.         procedure change_degree_method;
  212.  
  213.         procedure update_degrees;
  214.  
  215.         procedure update_edit_boxes;
  216.         procedure update_ra_edit_boxes;
  217.         procedure update_dec_edit_boxes;
  218.  
  219.         { events }
  220.         procedure FormShow(
  221.             Sender:TObject);
  222.  
  223.         procedure adjust;
  224.  
  225.         procedure check_activate(
  226.             Sender: TObject);
  227.  
  228.         procedure east_labelClick(
  229.             Sender: TObject);
  230.  
  231.         procedure west_labelClick(
  232.             Sender: TObject);
  233.  
  234.         procedure north_labelClick(
  235.             Sender: TObject);
  236.  
  237.         procedure south_labelClick(
  238.             Sender: TObject);
  239.  
  240.         procedure disconnect_from_scope_click(
  241.             Sender:TObject);
  242.  
  243.         procedure connect_to_scope_click(
  244.             sender:tobject);
  245.  
  246.         procedure goto_buttonClick(
  247.             Sender: TObject);
  248.  
  249.         procedure window_move_buttonClick(
  250.             Sender: TObject);
  251.  
  252.         procedure degree_move_buttonClick(
  253.             Sender: TObject);
  254.  
  255.         procedure window_trackChange(
  256.             Sender: TObject);
  257.  
  258.         procedure degrees_editKeyPress(
  259.                     Sender: TObject;
  260.             var Key: Char);
  261.  
  262.         procedure move_degrees_editKeyPress(
  263.                     Sender: TObject;
  264.             var Key: Char);
  265.  
  266.         procedure move_minutes_editKeyPress(
  267.                     Sender: TObject;
  268.             var Key: Char);
  269.  
  270.         procedure move_seconds_editKeyPress(
  271.                     Sender: TObject;
  272.             var Key: Char);
  273.  
  274.         procedure move_degrees_up_downChanging(
  275.                     Sender: TObject;
  276.             var AllowChange: Boolean);
  277.  
  278.         procedure move_minutes_up_downChanging(
  279.                     Sender: TObject;
  280.             var AllowChange: Boolean);
  281.  
  282.         procedure move_seconds_up_downChanging(
  283.                     Sender: TObject;
  284.             var AllowChange: Boolean);
  285.  
  286.         procedure move_degrees_editEnter(
  287.             Sender: TObject);
  288.  
  289.         procedure ra_hours_editKeyPress(
  290.                     Sender: TObject;
  291.             var Key: Char);
  292.  
  293.         procedure ra_minutes_editKeyPress(
  294.                     Sender: TObject;
  295.             var Key: Char);
  296.  
  297.         procedure ra_seconds_editKeyPress(
  298.                     Sender: TObject;
  299.             var Key: Char);
  300.  
  301.         procedure dec_degrees_editKeyPress(
  302.                     Sender: TObject;
  303.             var Key: Char);
  304.  
  305.         procedure dec_minutes_editKeyPress(
  306.                     Sender: TObject;
  307.             var Key: Char);
  308.  
  309.         procedure dec_seconds_editKeyPress(
  310.                     Sender: TObject;
  311.             var Key: Char);
  312.  
  313.         procedure ra_hours_up_downChanging(
  314.                     Sender: TObject;
  315.             var AllowChange: Boolean);
  316.  
  317.         procedure ra_minutes_up_downChanging(
  318.                     Sender: TObject;
  319.             var AllowChange: Boolean);
  320.  
  321.         procedure ra_seconds_up_downChanging(
  322.                     Sender: TObject;
  323.             var AllowChange: Boolean);
  324.  
  325.         procedure dec_degrees_up_downChanging(
  326.                     Sender: TObject;
  327.             var AllowChange: Boolean);
  328.  
  329.         procedure dec_minutes_up_downChanging(
  330.                     Sender: TObject;
  331.             var AllowChange: Boolean);
  332.  
  333.         procedure dec_seconds_up_downChanging(
  334.                     Sender: TObject;
  335.             var AllowChange: Boolean);
  336.  
  337.         procedure move_degrees_editChange(
  338.             Sender: TObject);
  339.  
  340.         procedure move_minutes_editChange(
  341.             Sender: TObject);
  342.  
  343.         procedure move_seconds_editChange(
  344.             Sender: TObject);
  345.  
  346.     private
  347.         { Private declarations }
  348.         north_south_reversed,
  349.         east_west_reversed:boolean;
  350.     public
  351.         { Public declarations }
  352.         moving_scope:boolean;
  353.         scope_name:shortstring;
  354.         ignore_event_north,
  355.         ignore_event_south,
  356.         ignore_event_west,
  357.         ignore_event_east:longint;
  358.         can_slew,
  359.         can_goto,
  360.         can_sync:boolean;
  361.         { configuration }
  362.         dimensions:dimensions_record;
  363.         { slew controls }
  364.         move_method:integer;
  365.         { window method }
  366.         window_percent:extended;
  367.         { degree method }
  368.         move_degrees,
  369.         move_minutes,
  370.         move_seconds:extended;
  371.         degrees_updating,
  372.         minutes_updating,
  373.         seconds_updating,
  374.         ra_hours_updating,
  375.         ra_minutes_updating,
  376.         ra_seconds_updating,
  377.         dec_degrees_updating,
  378.         dec_minutes_updating,
  379.         dec_seconds_updating:boolean;
  380.  
  381.         procedure normalise(
  382.                     max_degrees:integer;
  383.             var degrees,
  384.                     minutes,
  385.                     seconds:extended);
  386.  
  387.         { events }
  388.         procedure check_visible_and_show_hide(
  389.             sender:tobject);
  390.  
  391.         procedure hide_form;
  392.         procedure show_form;
  393.     end;
  394.  
  395. { global variables }
  396. var
  397.     scope_control:Tscope_control;
  398.  
  399. implementation
  400.  
  401. uses
  402.     ntc_ciel_client_network,
  403.     ntc_ciel_client_info,
  404.     ntc_ciel_client_focus,
  405.     ntc_ciel_client_tracking,
  406.     ntc_ciel_client_object,
  407.     ntc_ciel_client_search;
  408.  
  409. {$R *.dfm}
  410.  
  411.     { -------------
  412.         form controls
  413.         ------------- }
  414.  
  415. procedure tscope_control.formcreate(
  416.     Sender:TObject);
  417. begin
  418.     ignore_event_north:=event_0;
  419.     ignore_event_south:=event_0;
  420.     ignore_event_east:=event_0;
  421.     ignore_event_west:=event_0;
  422.     flip_buttons(false);
  423.     move_degrees_up_down.max:=max_degrees-1;
  424.     move_minutes_up_down.max:=minutes_in_degree-1;
  425.     move_seconds_up_down.max:=seconds_in_minute-1;
  426.     move_degrees_up_down.min:=0;
  427.     move_minutes_up_down.min:=0;
  428.     move_seconds_up_down.min:=0;
  429.     { goto }
  430.     ra_hours_up_down.min:=0;
  431.     ra_minutes_up_down.min:=0;
  432.     ra_seconds_up_down.min:=0;
  433.     dec_degrees_up_down.min:=0;
  434.     dec_minutes_up_down.min:=0;
  435.     dec_seconds_up_down.min:=0;
  436.     ra_hours_up_down.max:=max_hours-1;
  437.     ra_minutes_up_down.max:=minutes_in_degree-1;
  438.     ra_seconds_up_down.max:=seconds_in_minute-1;
  439.     dec_degrees_up_down.max:=max_degrees_dec-1;
  440.     dec_minutes_up_down.max:=minutes_in_degree-1;
  441.     dec_seconds_up_down.max:=seconds_in_minute-1;
  442.     { temporary }
  443.     can_slew:=true;
  444.     window_track.min:=0;
  445.     window_track.max:=window_track_max;
  446.     degrees_updating:=false;
  447.     minutes_updating:=false;
  448.     seconds_updating:=false;
  449.     ra_hours_updating:=false;
  450.     ra_minutes_updating:=false;
  451.     ra_seconds_updating:=false;
  452.     dec_degrees_updating:=false;
  453.     dec_minutes_updating:=false;
  454.     dec_seconds_updating:=false;
  455.     load_settings;
  456.     moving_scope:=false;
  457.     visible:=false;
  458. end;
  459.  
  460. procedure Tscope_control.form_close_query(
  461.             Sender: TObject;
  462.     var CanClose: Boolean);
  463. begin
  464.     visible:=false;
  465.     with dimensions do
  466.         begin
  467.             form_top:=top;
  468.             form_left:=left;
  469.         end;
  470.     if ciel_closing then
  471.         canclose:=true
  472.     else
  473.         canclose:=false;
  474. end;
  475.  
  476.     { -------------
  477.         scope linkage
  478.         ------------- }
  479.  
  480. procedure Tscope_control.flip_buttons(
  481.     toggle:boolean);
  482. begin
  483.     slew_group.enabled:=toggle;
  484.     if toggle then
  485.         begin
  486.             if move_method=window_method then
  487.                 change_window_method
  488.             else
  489.                 change_degree_method;
  490.         end
  491.     else
  492.         begin
  493.             move_window_group.enabled:=false;
  494.             move_units_group.Enabled:=false;
  495.         end;
  496.     east_button.enabled:=toggle;
  497.     north_button.enabled:=toggle;
  498.     west_button.enabled:=toggle;
  499.     south_button.enabled:=toggle;
  500.     stop_button.enabled:=toggle;
  501.     goto_group.enabled:=toggle;
  502. end;
  503.  
  504. function send_request(
  505.     m,
  506.     e:string)
  507.     :response_type;
  508. begin
  509.     result:=scope_network.send_request(m,e);
  510. end;
  511.  
  512. function send_request_check(
  513.     m:string)
  514.     :response_type;
  515. begin
  516.     result:=scope_network.send_request_check(m);
  517. end;
  518.  
  519. procedure Tscope_control.change_panel(
  520.     toggle:boolean);
  521. begin
  522.     if toggle then
  523.         begin
  524.             if not moving_scope then
  525.                 begin
  526.                     led_display.color:=clRed;
  527.                     led_display.refresh;
  528.                 end;
  529.             if can_slew then
  530.                 flip_buttons(true);
  531.             with scope_focus do
  532.                  if can_focus then
  533.                 begin
  534.                     update_speed_group(
  535.                         speed_box,
  536.                         first_speed_button,
  537.                         start_focus_speed,
  538.                         focus_speeds,
  539.                         speed_button_click,
  540.                         can_focus);
  541.                     flip_buttons(true);
  542.                 end
  543.             else
  544.                 flip_buttons(false);
  545.             with scope_tracking do
  546.                  if can_track then
  547.                 flip_buttons(true);
  548.             scope_search.enable_panel;
  549.             if not moving_scope then
  550.                 begin
  551.                     led_display.color:=clLime;
  552.                     led_display.refresh;
  553.                 end;
  554.             connect_button.Enabled:=not toggle;
  555.             disconnect_button.enabled:=toggle;
  556.         end
  557.     else
  558.         begin
  559.             scope_focus.flip_buttons(false);
  560.             scope_tracking.flip_buttons(false);
  561.             scope_search.disable_panel;
  562.             flip_buttons(false);
  563.             if not moving_scope then
  564.                 begin
  565.                     led_display.color:=clred;
  566.                     led_display.refresh;
  567.                     connect_button.Enabled:=not toggle;
  568.                 end;
  569.             disconnect_button.enabled:=toggle;
  570.         end;
  571.     if scope_focus.focused then
  572.         scope_focus.show;
  573.     if focused then
  574.         Show;
  575. end;
  576.  
  577. function Tscope_control.connect_to_scope
  578.     :boolean;
  579. begin
  580.     if send_request('connect','Connection to scope failed')>=[exit_ok] then
  581.         begin
  582.             scope_info.get_info;
  583.             change_panel(true);
  584.             result:=true;
  585.         end
  586.     else
  587.         result:=false;
  588. end;
  589.  
  590. function tscope_control.disconnect_from_scope
  591.     :boolean;
  592. begin
  593.     if send_request_check('disconnect')>=[exit_ok] then
  594.          with scope_control do
  595.         begin
  596.             led_display.color:=clRed;
  597.             led_display.refresh;
  598.             change_panel(false);
  599.             if focused then
  600.                 show;
  601.             result:=true;
  602.         end
  603.     else
  604.         result:=false;
  605. end;
  606.  
  607.     { -------------------
  608.         directional buttons
  609.         ------------------- }
  610.  
  611. procedure tscope_control.stop_failed;
  612. begin
  613.     showmessage(stop_error);
  614. end;
  615.  
  616. procedure tscope_control.move_down;
  617. begin
  618.     scope_search.move_screen('down');
  619. end;
  620.  
  621. procedure tscope_control.move_up;
  622. begin
  623.     scope_search.move_screen('up');
  624. end;
  625.  
  626. procedure tscope_control.move_left;
  627. begin
  628.     scope_search.move_screen('left');
  629. end;
  630.  
  631. procedure tscope_control.move_right;
  632. begin
  633.     scope_search.move_screen('right');
  634. end;
  635.  
  636. procedure tscope_control.move_distance(
  637.     d:string);
  638. var
  639.     t_ra:double;
  640. begin
  641.     t_ra:=move_seconds/seconds_in_minute;
  642.     t_ra:=(t_ra+move_minutes)/minutes_in_degree;
  643.     t_ra:=t_ra+move_degrees;
  644.     scope_network.send_request_check('move_'+d+'(distance='+floattostr(t_ra)+')');
  645.     scope_search.enable_timer;
  646. end;
  647.  
  648. procedure tscope_control.north_button_down(
  649.     Sender:TObject);
  650. begin
  651.     if not moving_scope then
  652.         begin
  653.             moving_scope:=true;
  654.             write_status_log('north - begin');
  655.             if move_method=window_method then
  656.                 begin
  657.                     if north_label.caption='N' then
  658.                         move_up
  659.                     else
  660.                         move_down;
  661.                 end
  662.             else if move_degrees+move_minutes+move_seconds>0 then
  663.                 move_distance('up')
  664.             else
  665.                 moving_scope:=false;
  666.             write_status_log('north - end');
  667.         end;
  668. end;
  669.  
  670. procedure tscope_control.south_button_down(
  671.     Sender:TObject);
  672. begin
  673.     if not moving_scope then
  674.         begin
  675.             moving_scope:=true;
  676.             write_status_log('south - begin');
  677.             if move_method=window_method then
  678.                 begin
  679.                     if north_label.caption='S' then
  680.                         move_up
  681.                     else
  682.                         move_down;
  683.                 end
  684.             else if move_degrees+move_minutes+move_seconds>0 then
  685.                 move_distance('down')
  686.             else
  687.                 moving_scope:=false;
  688.             write_status_log('south - end');
  689.         end;
  690. end;
  691.  
  692. procedure tscope_control.east_button_down(
  693.     Sender:TObject);
  694. begin
  695.     if not moving_scope then
  696.         begin
  697.             moving_scope:=true;
  698.             write_status_log('east - begin');
  699.             if move_method=window_method then
  700.                 begin
  701.                     if north_label.caption='W' then
  702.                         move_left
  703.                     else
  704.                         move_right;
  705.                 end
  706.             else if move_degrees+move_minutes+move_seconds>0 then
  707.                 move_distance('right')
  708.             else
  709.                 moving_scope:=false;
  710.             write_status_log('east - end');
  711.         end;
  712. end;
  713.  
  714. procedure tscope_control.west_button_down(
  715.     Sender:TObject);
  716. begin
  717.     if not moving_scope then
  718.         begin
  719.             moving_scope:=true;
  720.             write_status_log('west - begin');
  721.             if move_method=window_method then
  722.                 begin
  723.                     if north_label.caption='E' then
  724.                         move_left
  725.                     else
  726.                         move_right;
  727.                 end
  728.             else if move_degrees+move_minutes+move_seconds>0 then
  729.                 move_distance('left')
  730.             else
  731.                 moving_scope:=false;
  732.             write_status_log('west - end');
  733.         end;
  734. end;
  735.  
  736. procedure tscope_control.stop_scope;
  737. begin
  738.     if not (send_request_check('stop')>=[exit_ok]) then
  739.         stop_failed;
  740. end;
  741.  
  742. procedure tscope_control.stop_button_down(
  743.     Sender:TObject);
  744. begin
  745.     stop_scope;
  746. end;
  747.  
  748.     { ----
  749.         goto
  750.         ---- }
  751.  
  752. procedure tscope_control.go_to;
  753. begin
  754.     with current_object do
  755.         begin
  756.             ra:=strtointdef(ra_seconds_edit.text,0)/60;
  757.             ra:=(ra+strtointdef(ra_minutes_edit.text,0)/60);
  758.             ra:=ra+strtointdef(ra_hours_edit.text,0);
  759.             dec:=strtointdef(dec_seconds_edit.text,0)/60;
  760.             dec:=(dec+strtointdef(dec_minutes_edit.text,0)/60);
  761.             dec:=dec+strtointdef(dec_degrees_edit.text,0);
  762.             send_request_check('goto(ra='+floattostr(ra)+',dec='+floattostr(dec)+')');
  763.         end;
  764. end;
  765.  
  766.     { --------------
  767.         speed controls
  768.         -------------- }
  769.  
  770. procedure tscope_control.update_speed_group(
  771.     speed_box:tpanel;
  772.     first_speed_button:tspeedbutton;
  773.     start_speed,
  774.     speed_count:integer;
  775.     event:TNotifyEvent;
  776.     can_do:boolean);
  777. var
  778.     c,i,j,k,bh,bw,bl,bt:integer;
  779.     n,l,r,t:tspeedbutton;
  780.     x,y:extended;
  781. begin
  782.     if can_do then
  783.          with speed_box do
  784.         begin
  785.             r:=first_speed_button;
  786.             n:=tspeedbutton(r.tag);
  787.             i:=speed_count;
  788.             while n<>nil do
  789.                 begin
  790.                     l:=n;
  791.                     n:=tspeedbutton(n.tag);
  792.                     dec(i);
  793.                     if i<=0 then
  794.                         begin
  795.                             if i=0 then
  796.                                 begin
  797.                                     t:=tspeedbutton(r.tag);
  798.                                     r.Tag:=longint(nil);
  799.                                     r:=t;
  800.                                 end
  801.                             else
  802.                                 r:=tspeedbutton(r.tag);
  803.                             l.free;
  804.                         end
  805.                     else
  806.                         r:=tspeedbutton(r.tag);
  807.                 end;
  808.             while i>1 do
  809.                 begin
  810.                     r.tag:=longint(tspeedbutton.create(self));
  811.                     r:=tspeedbutton(r.tag);
  812.                     r.tag:=longint(nil);
  813.                     r.Parent:=speed_box;
  814.                     dec(i);
  815.                 end;
  816.             x:=speed_count;
  817.             i:=trunc(sqrt(x));
  818.             if i>1 then
  819.                 begin
  820.                     y:=sqr(i+1);
  821.                     j:=trunc(sqrt(y));
  822.                     k:=speed_count div j;
  823.                     if (k>=i) and (speed_count mod j<>0) then
  824.                         begin
  825.                             k:=-1;
  826.                             inc(i);
  827.                         end;
  828.                 end
  829.             else
  830.                 k:=0;
  831.             if height>=width then
  832.                 begin
  833.                     if i<=1 then
  834.                         begin
  835.                             if speed_count>1 then
  836.                                 bh:=height div speed_count
  837.                             else
  838.                                 begin
  839.                                     bh:=height;
  840.                                     i:=1
  841.                                 end;
  842.                         end
  843.                     else if (k>=0) and ((speed_count mod i<>0) or (k>=i)) then
  844.                         bh:=height div (i+1)
  845.                     else
  846.                         bh:=height div i;
  847.                     n:=first_speed_button;
  848.                     if i>1 then
  849.                         bw:=width div i
  850.                     else
  851.                         begin
  852.                             bw:=width;
  853.                             n.Caption:=inttostr(start_speed);
  854.                         end;
  855.                 end
  856.             else
  857.                 begin
  858.                     if i<=1 then
  859.                         begin
  860.                             if speed_count>1 then
  861.                                 bw:=width div speed_count
  862.                             else
  863.                                 begin
  864.                                     bw:=width;
  865.                                     i:=1
  866.                                 end;
  867.                         end
  868.                     else if (k>=0) and ((speed_count mod i<>0) or (k>=i)) then
  869.                         bw:=width div (i+1)
  870.                     else
  871.                         bw:=width div i;
  872.                     n:=first_speed_button;
  873.                     if i>1 then
  874.                         bh:=height div i
  875.                     else
  876.                         begin
  877.                             bh:=height;
  878.                             n.Caption:=inttostr(start_speed);
  879.                         end;
  880.                 end;
  881.             bl:=0;
  882.             bt:=0;
  883.             c:=start_speed;
  884.             while n<>nil do
  885.                  with n do
  886.                 begin
  887.                     Width:=bw;
  888.                     top:=bt;
  889.                     left:=bl;
  890.                     inc(bl,bw);
  891.                     with speed_box do
  892.                          if height>=width then
  893.                         begin
  894.                             if bl+(bw div 2)>width then
  895.                                 begin
  896.                                     bl:=0;
  897.                                     inc(bt,bh);
  898.                                 end;
  899.                         end
  900.                     else if bt+(bh div 2)>Height then
  901.                         begin
  902.                             bt:=0;
  903.                             inc(bl,bw);
  904.                         end;
  905.                     Height:=bh;
  906.                     down:=false;
  907.                     groupindex:=1;
  908.                     allowallup:=false;
  909.                     caption:=inttostr(c);
  910.                     visible:=true;
  911.                     enabled:=true;
  912.                     onclick:=event;
  913.                     inc(c);
  914.                     n:=tspeedbutton(Tag);
  915.                 end;
  916.             first_speed_button.down:=true;
  917.         end;
  918. end;
  919.  
  920. function tscope_control.set_slew_speed(
  921.     speed_box:tpanel)
  922.     :integer;
  923. var
  924.     i:integer;
  925. begin
  926.     result:=1;
  927.     for I:= 0 to speed_box.ControlCount -1 do
  928.         begin
  929.             if tspeedbutton(speed_box.controls[i]).down=true then
  930.                 begin
  931.                     result:=strtointdef(tspeedbutton(speed_box.controls[i]).caption,i+1);
  932.                     exit;
  933.                 end;
  934.         end;
  935. end;
  936.  
  937.     { -------
  938.         logging
  939.         ------- }
  940.  
  941. procedure tscope_control.write_status_log(
  942.     e:string);
  943. begin
  944.     scope_network.write_status_log_check(e);
  945. end;
  946.  
  947.     { -------------
  948.         configuration
  949.         ------------- }
  950.  
  951. procedure tscope_control.load_settings;
  952. begin
  953.     ini_file:=tinifile.create(application_path+'ciel.ini');
  954.     with ini_file do
  955.         begin
  956.             move_method:=readinteger('control','move_method',window_method);
  957.             window_percent:=
  958.                 readfloat('control','window_percent',window_percent_default);
  959.             move_degrees:=readfloat('control','move_degrees',move_degrees_default);
  960.             move_minutes:=readfloat('control','move_minutes',move_minutes_default);
  961.             move_seconds:=readfloat('control','move_seconds',move_seconds_default);
  962.             window_track.Position:=trunc(window_percent) div window_track_step;
  963.             degrees_edit.text:=floattostr(window_percent);
  964.             update_degrees;
  965.             move_degrees_up_down.position:=trunc(move_degrees);
  966.             move_minutes_up_down.position:=trunc(move_minutes);
  967.             move_seconds_up_down.position:=trunc(move_seconds);
  968.             if move_method=window_method then
  969.                 window_move_button.down:=true
  970.             else
  971.                 degree_move_button.down:=true;
  972.             north_south_reversed:=ReadBool('control','swap_north_south',false);
  973.             east_west_reversed:=ReadBool('control','swap_east_west',false);
  974.             can_goto:=ReadBool('control','can_goto',false);
  975.             can_sync:=ReadBool('control','can_sync',false);
  976.             if north_south_reversed then
  977.                 begin
  978.                     north_label.Caption:='S';
  979.                     south_label.caption:='N';
  980.                 end
  981.             else
  982.                 begin
  983.                     north_label.Caption:='N';
  984.                     south_label.caption:='S';
  985.                 end;
  986.             if east_west_reversed then
  987.                 begin
  988.                     east_label.Caption:='W';
  989.                     west_label.caption:='E';
  990.                 end
  991.             else
  992.                 begin
  993.                     east_label.Caption:='E';
  994.                     west_label.caption:='W';
  995.                 end;
  996.             locked_check.checked:=true;
  997.             { form }
  998.             scope.get_dimensions(scope_control,@dimensions,'control',ini_file);
  999.             left:=dimensions.form_left;
  1000.             top:=dimensions.form_top;
  1001.             visible:=readbool('control','visible',false);
  1002.         end;
  1003.     ini_file.free;
  1004. end;
  1005.  
  1006. procedure tscope_control.save_settings;
  1007. begin
  1008.     with ini_file do
  1009.         begin
  1010.             writeinteger('control','move_method',move_method);
  1011.             writefloat('control','window_percent',window_percent);
  1012.             writefloat('control','move_degrees',move_degrees);
  1013.             writefloat('control','move_minutes',move_minutes);
  1014.             writefloat('control','move_seconds',move_seconds);
  1015.             writeBool('control','swap_north_south',north_south_reversed);
  1016.             writeBool('control','swap_east_west',east_west_reversed);
  1017.             writeBool('control','can_goto',can_goto);
  1018.             writeBool('control','can_sync',can_sync);
  1019.             { form }
  1020.             scope.find_vdu(scope_control,@dimensions);
  1021.             scope.write_dimensions(@dimensions,left,top,'control',ini_file);
  1022.             writebool('control','visible',visible);
  1023.         end;
  1024. end;
  1025.  
  1026.     { --------
  1027.         utilites
  1028.         -------- }
  1029.  
  1030. procedure Tscope_control.change_window_method;
  1031. begin
  1032.     move_units_group.enabled:=false;
  1033.     move_degrees_edit.enabled:=false;
  1034.     move_minutes_edit.enabled:=false;
  1035.     move_seconds_edit.enabled:=false;
  1036.     move_degrees_up_down.Enabled:=false;
  1037.     move_minutes_up_down.Enabled:=false;
  1038.     move_seconds_up_down.Enabled:=false;
  1039.     move_degrees_label.Enabled:=false;
  1040.     move_minutes_label.Enabled:=false;
  1041.     move_seconds_label.Enabled:=false;
  1042.     window_track.Enabled:=true;
  1043.     degrees_edit.enabled:=true;
  1044.     move_window_group.enabled:=true;
  1045.     move_method:=window_method;
  1046.     window_move_button.down:=true;
  1047. end;
  1048.  
  1049. procedure Tscope_control.change_degree_method;
  1050. begin
  1051.     move_window_group.enabled:=false;
  1052.     window_track.Enabled:=false;
  1053.     degrees_edit.enabled:=false;
  1054.     move_degrees_edit.enabled:=true;
  1055.     move_minutes_edit.enabled:=true;
  1056.     move_seconds_edit.enabled:=true;
  1057.     move_degrees_up_down.Enabled:=true;
  1058.     move_minutes_up_down.Enabled:=true;
  1059.     move_seconds_up_down.Enabled:=true;
  1060.     move_degrees_label.Enabled:=true;
  1061.     move_minutes_label.Enabled:=true;
  1062.     move_seconds_label.Enabled:=true;
  1063.     move_units_group.enabled:=true;
  1064.     move_method:=degree_method;
  1065.     degree_move_button.down:=true;
  1066. end;
  1067.  
  1068. procedure Tscope_control.normalise(
  1069.             max_degrees:integer;
  1070.     var degrees,
  1071.             minutes,
  1072.             seconds:extended);
  1073. begin
  1074.     if (degrees>0) and (degrees>=max_degrees) then
  1075.         degrees:=max_degrees-1
  1076.     else if (degrees<0) and (degrees<=-max_degrees) then
  1077.         degrees:=-(max_degrees-1);
  1078.     if frac(degrees)<>0 then
  1079.         begin
  1080.             minutes:=0;
  1081.             seconds:=0;
  1082.             minutes:=frac(degrees)*minutes_in_degree;
  1083.             degrees:=trunc(degrees);
  1084.             seconds:=frac(minutes)*seconds_in_minute;
  1085.             minutes:=trunc(minutes);
  1086.         end
  1087.     else if frac(minutes)<>0 then
  1088.         begin
  1089.             seconds:=0;
  1090.             seconds:=frac(minutes)*seconds_in_minute;
  1091.             minutes:=trunc(minutes);
  1092.         end;
  1093. end;
  1094.  
  1095. procedure Tscope_control.update_degrees;
  1096. begin
  1097.     normalise(max_degrees,move_degrees,move_minutes,move_seconds);
  1098. end;
  1099.  
  1100. procedure Tscope_control.update_edit_boxes;
  1101. begin
  1102.     move_degrees:=strtofloatdef(move_degrees_edit.text,move_degrees);
  1103.     move_minutes:=strtofloatdef(move_minutes_edit.text,move_minutes);
  1104.     move_seconds:=strtofloatdef(move_seconds_edit.text,move_seconds);
  1105.     update_degrees;
  1106.     move_degrees_edit.text:=floattostr(move_degrees);
  1107.     move_minutes_edit.Text:=floattostr(move_minutes);
  1108.     move_seconds_edit.text:=floattostr(move_seconds);
  1109.     move_degrees_up_down.position:=trunc(move_degrees);
  1110.     move_minutes_up_down.position:=trunc(move_minutes);
  1111.     move_seconds_up_down.position:=trunc(move_seconds);
  1112. end;
  1113.  
  1114.     { ------
  1115.         events
  1116.         ------ }
  1117.  
  1118. procedure Tscope_control.FormShow(
  1119.     Sender:TObject);
  1120. begin
  1121.     with dimensions do
  1122.         begin
  1123.             top:=form_top;
  1124.             left:=form_left;
  1125.         end;
  1126. end;
  1127.  
  1128. procedure tscope_control.adjust;
  1129. begin
  1130.     with dimensions do
  1131.         begin
  1132.             form_top:=trunc(form_top/last_screen_height*current_height);
  1133.             form_left:=trunc(form_left/last_screen_width*current_width);
  1134.         end;
  1135.     if visible then
  1136.         show;
  1137. end;
  1138.  
  1139. procedure tscope_control.check_visible_and_show_hide(
  1140.     sender:tobject);
  1141. begin
  1142.     if visible then
  1143.         hide_form
  1144.     else
  1145.         show_form;
  1146.     scope.show_hide(sender,visible);
  1147. end;
  1148.  
  1149. procedure tscope_control.hide_form;
  1150. begin
  1151.     with dimensions do
  1152.         begin
  1153.             form_top:=top;
  1154.             form_left:=left;
  1155.         end;
  1156.     Visible:=false;
  1157.     formstyle:=fsnormal;
  1158. end;
  1159.  
  1160. procedure tscope_control.show_form;
  1161. begin
  1162.     formstyle:=fsstayontop;
  1163.     Visible:=true;
  1164. end;
  1165.  
  1166. procedure Tscope_control.check_activate(
  1167.     Sender: TObject);
  1168. begin
  1169.     scope.form_activate(scope_control,@dimensions);
  1170. end;
  1171.  
  1172. procedure Tscope_control.east_labelClick(
  1173.     Sender: TObject);
  1174. begin
  1175.     if not locked_check.checked then
  1176.         begin
  1177.             east_west_reversed:=east_label.caption='E';
  1178.             if east_west_reversed then
  1179.                 begin
  1180.                     east_label.caption:='W';
  1181.                     west_label.caption:='E';
  1182.                 end
  1183.             else
  1184.                 begin
  1185.                     east_label.caption:='E';
  1186.                     west_label.caption:='W';
  1187.                 end;
  1188.         end;
  1189. end;
  1190.  
  1191. procedure Tscope_control.west_labelClick(
  1192.     Sender: TObject);
  1193. begin
  1194.     if not locked_check.checked then
  1195.         begin
  1196.             east_west_reversed:=west_label.caption='W';
  1197.             if east_west_reversed then
  1198.                 begin
  1199.                     east_label.caption:='W';
  1200.                     west_label.caption:='E';
  1201.                 end
  1202.             else
  1203.                 begin
  1204.                     east_label.caption:='E';
  1205.                     west_label.caption:='W';
  1206.                 end;
  1207.         end;
  1208. end;
  1209.  
  1210. procedure Tscope_control.north_labelClick(
  1211.     Sender: TObject);
  1212. begin
  1213.     if not locked_check.checked then
  1214.         begin
  1215.             north_south_reversed:=north_label.caption='N';
  1216.             if north_south_reversed then
  1217.                 begin
  1218.                     north_label.caption:='S';
  1219.                     south_label.caption:='N';
  1220.                 end
  1221.             else
  1222.                 begin
  1223.                     north_label.caption:='N';
  1224.                     south_label.caption:='S';
  1225.                 end;
  1226.         end;
  1227. end;
  1228.  
  1229. procedure Tscope_control.south_labelClick(
  1230.     Sender: TObject);
  1231. begin
  1232.     if not locked_check.checked then
  1233.         begin
  1234.             north_south_reversed:=south_label.caption='S';
  1235.             if north_south_reversed then
  1236.                 begin
  1237.                     north_label.caption:='S';
  1238.                     south_label.caption:='N';
  1239.                 end
  1240.             else
  1241.                 begin
  1242.                     north_label.caption:='N';
  1243.                     south_label.caption:='S';
  1244.                 end;
  1245.         end;
  1246. end;
  1247.  
  1248. procedure tscope_control.connect_to_scope_click(
  1249.     sender:tobject);
  1250. begin
  1251.     if scope_network.scope_client.connected and not moving_scope then
  1252.         connect_to_scope;
  1253. end;
  1254.  
  1255. procedure Tscope_control.disconnect_from_scope_click(
  1256.     Sender:TObject);
  1257. begin
  1258.     if scope_network.scope_client.connected and not moving_scope then
  1259.         disconnect_from_scope;
  1260. end;
  1261.  
  1262. procedure Tscope_control.goto_buttonClick(
  1263.     Sender: TObject);
  1264. begin
  1265.     go_to;
  1266. end;
  1267.  
  1268. procedure Tscope_control.degrees_editKeyPress(
  1269.             Sender: TObject;
  1270.     var Key: Char);
  1271. var
  1272.     t:extended;
  1273. begin
  1274.     if key=cr then
  1275.         begin
  1276.             t:=strtofloatdef(degrees_edit.text,0.5);
  1277.             if (t<=100) and (t>=0) then
  1278.                 begin
  1279.                     move_degrees:=t;
  1280.                     window_track.position:=trunc(t) div window_track_step;
  1281.                 end;
  1282.         end;
  1283. end;
  1284.  
  1285. procedure Tscope_control.window_trackChange(
  1286.     Sender: TObject);
  1287. begin
  1288.     with window_track do
  1289.         begin
  1290.             window_percent:=position*window_track_step;
  1291.             degrees_edit.text:=floattostr(window_percent);
  1292.         end;
  1293. end;
  1294.  
  1295. procedure Tscope_control.window_move_buttonClick(
  1296.     Sender: TObject);
  1297. begin
  1298.     change_window_method;
  1299. end;
  1300.  
  1301. procedure Tscope_control.degree_move_buttonClick(
  1302.     Sender: TObject);
  1303. begin
  1304.     change_degree_method;
  1305. end;
  1306.  
  1307. procedure Tscope_control.move_degrees_editKeyPress(
  1308.             Sender: TObject;
  1309.     var Key: Char);
  1310. begin
  1311.     if key=cr then
  1312.         update_edit_boxes;
  1313. end;
  1314.  
  1315. procedure Tscope_control.move_minutes_editKeyPress(
  1316.             Sender: TObject;
  1317.     var Key: Char);
  1318. begin
  1319.     if key=cr then
  1320.         update_edit_boxes;
  1321. end;
  1322.  
  1323. procedure Tscope_control.move_seconds_editKeyPress(
  1324.             Sender: TObject;
  1325.     var Key: Char);
  1326. begin
  1327.     if key=cr then
  1328.         update_edit_boxes;
  1329. end;
  1330.  
  1331. procedure Tscope_control.move_degrees_up_downChanging(
  1332.             Sender: TObject;
  1333.     var AllowChange: Boolean);
  1334. begin
  1335.     if not degrees_updating then
  1336.         begin
  1337.             degrees_updating:=true;
  1338.             update_edit_boxes;
  1339.             degrees_updating:=false;
  1340.         end;
  1341. end;
  1342.  
  1343. procedure Tscope_control.move_minutes_up_downChanging(
  1344.             Sender: TObject;
  1345.     var AllowChange: Boolean);
  1346. begin
  1347.     if not minutes_updating then
  1348.         begin
  1349.             minutes_updating:=true;
  1350.             update_edit_boxes;
  1351.             minutes_updating:=false;
  1352.         end;
  1353. end;
  1354.  
  1355. procedure Tscope_control.move_seconds_up_downChanging(
  1356.             Sender: TObject;
  1357.     var AllowChange: Boolean);
  1358. begin
  1359.     if not seconds_updating then
  1360.         begin
  1361.             seconds_updating:=true;
  1362.             update_edit_boxes;
  1363.             seconds_updating:=false;
  1364.         end;
  1365. end;
  1366.  
  1367. procedure Tscope_control.move_degrees_editEnter(
  1368.     Sender: TObject);
  1369. begin
  1370.     update_edit_boxes;
  1371. end;
  1372.  
  1373. procedure Tscope_control.update_ra_edit_boxes;
  1374. var
  1375.     ra_h,ra_m,ra_s:extended;
  1376. begin
  1377.     ra_h:=strtofloatdef(ra_hours_edit.text,0);
  1378.     ra_m:=strtofloatdef(ra_minutes_edit.text,0);
  1379.     ra_s:=strtofloatdef(ra_seconds_edit.text,0);
  1380.     normalise(max_hours,ra_h,ra_m,ra_s);
  1381.     ra_hours_edit.text:=floattostr(ra_h);
  1382.     ra_minutes_edit.Text:=floattostr(ra_m);
  1383.     ra_seconds_edit.text:=floattostr(ra_s);
  1384.     ra_hours_up_down.position:=trunc(ra_h);
  1385.     ra_minutes_up_down.position:=trunc(ra_m);
  1386.     ra_seconds_up_down.position:=trunc(ra_s);
  1387. end;
  1388.  
  1389. procedure Tscope_control.ra_hours_editKeyPress(
  1390.             Sender: TObject;
  1391.     var Key: Char);
  1392. begin
  1393.     if key=cr then
  1394.         update_ra_edit_boxes;
  1395. end;
  1396.  
  1397. procedure Tscope_control.ra_minutes_editKeyPress(
  1398.             Sender: TObject;
  1399.     var Key: Char);
  1400. begin
  1401.     if key=cr then
  1402.         update_ra_edit_boxes;
  1403. end;
  1404.  
  1405. procedure Tscope_control.ra_seconds_editKeyPress(
  1406.             Sender: TObject;
  1407.     var Key: Char);
  1408. begin
  1409.     if key=cr then
  1410.         update_ra_edit_boxes;
  1411. end;
  1412.  
  1413. procedure Tscope_control.update_dec_edit_boxes;
  1414. var
  1415.     dec_d,dec_m,dec_s:extended;
  1416. begin
  1417.     dec_d:=strtofloatdef(dec_degrees_edit.text,0);
  1418.     dec_m:=strtofloatdef(dec_minutes_edit.text,0);
  1419.     dec_s:=strtofloatdef(dec_seconds_edit.text,0);
  1420.     normalise(max_degrees_dec,dec_d,dec_m,dec_s);
  1421.     dec_degrees_edit.text:=floattostr(dec_d);
  1422.     dec_minutes_edit.Text:=floattostr(dec_m);
  1423.     dec_seconds_edit.text:=floattostr(dec_s);
  1424.     dec_degrees_up_down.position:=trunc(dec_d);
  1425.     dec_minutes_up_down.position:=trunc(dec_m);
  1426.     dec_seconds_up_down.position:=trunc(dec_s);
  1427. end;
  1428.  
  1429. procedure Tscope_control.dec_degrees_editKeyPress(
  1430.             Sender: TObject;
  1431.     var Key: Char);
  1432. begin
  1433.     if key=cr then
  1434.         update_dec_edit_boxes;
  1435. end;
  1436.  
  1437. procedure Tscope_control.dec_minutes_editKeyPress(
  1438.             Sender: TObject;
  1439.     var Key: Char);
  1440. begin
  1441.     if key=cr then
  1442.         update_dec_edit_boxes;
  1443. end;
  1444.  
  1445. procedure Tscope_control.dec_seconds_editKeyPress(
  1446.             Sender: TObject;
  1447.     var Key: Char);
  1448. begin
  1449.     if key=cr then
  1450.         update_dec_edit_boxes;
  1451. end;
  1452.  
  1453. procedure Tscope_control.ra_hours_up_downChanging(
  1454.             Sender: TObject;
  1455.     var AllowChange: Boolean);
  1456. begin
  1457.     if not ra_hours_updating then
  1458.         begin
  1459.             ra_hours_updating:=true;
  1460.             update_ra_edit_boxes;
  1461.             ra_hours_updating:=false;
  1462.         end;
  1463. end;
  1464.  
  1465. procedure Tscope_control.ra_minutes_up_downChanging(
  1466.             Sender: TObject;
  1467.     var AllowChange: Boolean);
  1468. begin
  1469.     if not ra_minutes_updating then
  1470.         begin
  1471.             ra_minutes_updating:=true;
  1472.             update_ra_edit_boxes;
  1473.             ra_minutes_updating:=false;
  1474.         end;
  1475. end;
  1476.  
  1477. procedure Tscope_control.ra_seconds_up_downChanging(
  1478.             Sender: TObject;
  1479.     var AllowChange: Boolean);
  1480. begin
  1481.     if not ra_seconds_updating then
  1482.         begin
  1483.             ra_seconds_updating:=true;
  1484.             update_ra_edit_boxes;
  1485.             ra_seconds_updating:=false;
  1486.         end;
  1487. end;
  1488.  
  1489. procedure Tscope_control.dec_degrees_up_downChanging(
  1490.             Sender: TObject;
  1491.     var AllowChange: Boolean);
  1492. begin
  1493.     if not dec_degrees_updating then
  1494.         begin
  1495.             dec_degrees_updating:=true;
  1496.             update_dec_edit_boxes;
  1497.             dec_degrees_updating:=false;
  1498.         end;
  1499. end;
  1500.  
  1501. procedure Tscope_control.dec_minutes_up_downChanging(
  1502.             Sender: TObject;
  1503.     var AllowChange: Boolean);
  1504. begin
  1505.     if not dec_minutes_updating then
  1506.         begin
  1507.             dec_minutes_updating:=true;
  1508.             update_dec_edit_boxes;
  1509.             dec_minutes_updating:=false;
  1510.         end;
  1511. end;
  1512.  
  1513. procedure Tscope_control.dec_seconds_up_downChanging(
  1514.             Sender: TObject;
  1515.     var AllowChange: Boolean);
  1516. begin
  1517.     if not dec_seconds_updating then
  1518.         begin
  1519.             dec_seconds_updating:=true;
  1520.             update_dec_edit_boxes;
  1521.             dec_seconds_updating:=false;
  1522.         end;
  1523. end;
  1524.  
  1525. procedure Tscope_control.move_degrees_editChange(
  1526.     Sender: TObject);
  1527. begin
  1528.     update_edit_boxes;
  1529. end;
  1530.  
  1531. procedure Tscope_control.move_minutes_editChange(
  1532.     Sender: TObject);
  1533. begin
  1534.     update_edit_boxes;
  1535. end;
  1536.  
  1537. procedure Tscope_control.move_seconds_editChange(
  1538.     Sender: TObject);
  1539. begin
  1540.     update_edit_boxes;
  1541. end;
  1542.  
  1543. end.
  1544.  
  1545.